package com.gbr.view.areaselector;

import com.gbr.presentation.areaselector.IAreaSelectorPresentation;

import javafx.event.EventHandler;
import javafx.geometry.Rectangle2D;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.canvas.Canvas;
import javafx.scene.canvas.GraphicsContext;
import javafx.scene.input.KeyCode;
import javafx.scene.input.KeyEvent;
import javafx.scene.input.MouseButton;
import javafx.scene.input.MouseEvent;
import javafx.scene.paint.Color;
import javafx.scene.text.Font;
import javafx.scene.text.TextAlignment;
import javafx.stage.Screen;
import javafx.stage.Stage;
import javafx.stage.StageStyle;

public class AreaSelector extends Stage {
	private IAreaSelectorPresentation presentation;
	private Rectangle2D area;
	int x = 0;
	int y = 0;
	int width = 0;
	int height = 0;

	public AreaSelector(IAreaSelectorPresentation prez) {
		this.presentation = prez;
		initStyle(StageStyle.TRANSPARENT);
		test();
	}

	public void test() {
		Rectangle2D primaryScreenBounds = Screen.getPrimary().getVisualBounds();
		// set Stage boundaries to visible bounds of the main screen
		setX(primaryScreenBounds.getMinX());
		setY(primaryScreenBounds.getMinY());
		setWidth(primaryScreenBounds.getWidth());
		setHeight(primaryScreenBounds.getHeight());
		
		addEventHandler(KeyEvent.KEY_PRESSED, new EventHandler<KeyEvent>() {
			@Override
			public void handle(KeyEvent event) {
				if (event.getCode() == KeyCode.ESCAPE) {
					presentation.abort();
				}
			}
		});

		Canvas canvas = new Canvas(primaryScreenBounds.getWidth(),
				primaryScreenBounds.getHeight());
		drawRectangle(canvas);

		Group root = new Group();
		root.getChildren().add(canvas);
		setScene(new Scene(root, 0, 0, Color.rgb(0, 0, 0, 0.5)));
	}

	private void drawRectangle(final Canvas canvas) {
		final GraphicsContext gc = canvas.getGraphicsContext2D();
		final RubberBand band = new RubberBand();

		gc.setStroke(Color.WHITE);
		Font font = gc.getFont();
		gc.setFont(new Font(font.getName(), 24));
		
		canvas.setOnMousePressed(new EventHandler<MouseEvent>() {
			@Override
			public void handle(MouseEvent event) {
				if (event.getButton() == MouseButton.PRIMARY) {
					gc.clearRect(0, 0, canvas.getWidth(), canvas.getHeight());
					band.x = event.getX();
					band.y = event.getY();
				}
			}
		});
		canvas.setOnMouseDragged(new EventHandler<MouseEvent>() {
			@Override
			public void handle(MouseEvent mouseEvent) {
				if (mouseEvent.getButton() != MouseButton.PRIMARY) {
					return;
				}
				
				band.width = mouseEvent.getX() - band.x;
				band.height = mouseEvent.getY() - band.y;
				
				x = (int) Math.round(band.width < 0 ? mouseEvent.getX() : band.x);
				y = (int) Math.round(band.height < 0 ? mouseEvent.getY() : band.y);
				width = (int) Math.round(band.width < 0 ? band.x - mouseEvent.getX() : band.width);
				height = (int) Math.round(band.height < 0 ? band.y - mouseEvent.getY() : band.height);
				
				gc.clearRect(0, 0, canvas.getWidth(), canvas.getHeight());
				gc.setLineWidth(3);
				gc.setStroke(Color.BLACK);
				gc.strokeRect(x, y, width+2, height+2);
				gc.setStroke(Color.WHITE);
				gc.strokeRect(x, y, width, height);
				
				gc.setTextAlign(TextAlignment.LEFT);
				gc.setLineWidth(2);
				gc.setStroke(Color.BLACK);
		        gc.strokeText("[ "+width+"w, "+height+"h ]", x+2, y-8);
				gc.setStroke(Color.WHITE);
		        gc.strokeText("[ "+width+"w, "+height+"h ]", x, y-10);
			}
		});
		canvas.setOnMouseReleased(new EventHandler<MouseEvent>() {
			@Override
			public void handle(MouseEvent event) {
				if (event.getButton() == MouseButton.PRIMARY) {
					if (width > 0 && height > 0) {
						presentation.setRecordingArea(x, y, width, height);
					}
				} else if (event.getButton() == MouseButton.SECONDARY) {
					presentation.abort();
				}
			}
		});
	}
	
	public Rectangle2D getArea() {
		return area;
	}

	public void setArea(Rectangle2D area) {
		this.area = area;
	}

	class RubberBand {
		double x, y, width, height;
	}
}
